﻿namespace S4sme.Web.Areas.Blog.Controllers
{
    using System;
    using System.Linq;
    using System.Web.Mvc;

    using S4sme.Core.Extensions;
    using S4sme.Domain;
    using S4sme.Tasks.Blog;

    using SharpLite.Domain.DataInterfaces;

    public class AdminController : AuthorizeBaseController
    {
        private readonly IRepository<Post> postRepository;

        private readonly IRepository<Category> categoryRepository;

        private readonly IRepository<Tag> tagRepository;

        private readonly IRepository<Comment> commentRepository;

        private readonly PostCudTasks postTasks;

        private readonly CategoryCudTasks categoryTasks;

        private readonly TagCudTasks tagTasks;

        private readonly CommentCudTasks commentTasks;

        public AdminController(IRepository<Post> postRepository, IRepository<Category> categoryRepository, IRepository<Tag> tagRepository, IRepository<Comment> commentRepository, PostCudTasks postTasks, CategoryCudTasks categoryTasks, TagCudTasks tagTasks, CommentCudTasks commentTasks)
        {
            this.postRepository = postRepository;
            this.categoryRepository = categoryRepository;
            this.tagRepository = tagRepository;
            this.commentRepository = commentRepository;
            this.postTasks = postTasks;
            this.categoryTasks = categoryTasks;
            this.tagTasks = tagTasks;
            this.commentTasks = commentTasks;
        }

        //
        // GET: /Blog/Admin/

        public ActionResult Posts()
        {
            var posts = this.postRepository.GetAll();
            return View(posts);
        }

        public ActionResult CreatePost()
        {
            return this.View("EditPost", this.postTasks.CreateEditViewModel());
        }

        public ActionResult EditPost(int id)
        {
            return View(this.postTasks.CreateEditViewModel(id));
        }

        [HttpPost]
        /*[ValidateInput(false)]  allows HTML markup */
        [ValidateAntiForgeryToken]
        public ActionResult EditPost(Post post)
        {
            if (ModelState.IsValid)
            {
                // will be used only once the new post created
                post.Author = HttpContext.User.Identity.Name;
                post.CreatedDate = DateTime.Now;
                post.ModifiedDate = post.CreatedDate;
                post.Slug = post.Title.GenerateSlug();

                ActionConfirmation<Post> confirmation = this.postTasks.SaveOrUpdate(post);

                if (confirmation.WasSuccessful)
                {
                    TempData["message"] = confirmation.Message;
                    return RedirectToAction("Posts");
                }

                ViewData["message"] = confirmation.Message;
            }

            return View(this.postTasks.CreateEditViewModel(post));
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        public ActionResult DeletePost(int id)
        {
            ActionConfirmation<Post> confirmation = this.postTasks.Delete(id);
            TempData["message"] = confirmation.Message;
            return RedirectToAction("Posts");
        }

        public ActionResult Categories()
        {
            return View(this.categoryRepository.GetAll().OrderBy(pc => pc.Name));
        }

        public ActionResult CreateCategory()
        {
            return this.View("EditCategory", this.categoryTasks.CreateEditViewModel());
        }

        public ActionResult EditCategory(int id)
        {
            return View(this.categoryTasks.CreateEditViewModel(id));
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        public ActionResult EditCategory(Category category)
        {
            if (ModelState.IsValid)
            {
                var confirmation = this.categoryTasks.SaveOrUpdate(category);

                if (confirmation.WasSuccessful)
                {
                    TempData["message"] = confirmation.Message;
                    return RedirectToAction("Categories");
                }

                ViewData["message"] = confirmation.Message;
            }

            return View(this.categoryTasks.CreateEditViewModel(category));
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        public ActionResult DeleteCategory(int id)
        {
            var confirmation = this.categoryTasks.Delete(id);
            TempData["message"] = confirmation.Message;
            return RedirectToAction("Categories");
        }

        public ActionResult Tags()
        {
            return View(this.tagRepository.GetAll().OrderBy(t => t.Name));
        }

        public ActionResult CreateTag()
        {
            return this.View("EditTag", this.tagTasks.CreateEditViewModel());
        }

        public ActionResult EditTag(int id)
        {
            return View(this.tagTasks.CreateEditViewModel(id));
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        public ActionResult EditTag(Tag tag)
        {
            if (ModelState.IsValid)
            {
                var confirmation = this.tagTasks.SaveOrUpdate(tag);

                if (confirmation.WasSuccessful)
                {
                    TempData["message"] = confirmation.Message;
                    return RedirectToAction("Tags");
                }

                ViewData["message"] = confirmation.Message;
            }

            return View(this.tagTasks.CreateEditViewModel(tag));
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        public ActionResult DeleteTag(int id)
        {
            var confirmation = this.tagTasks.Delete(id);
            TempData["message"] = confirmation.Message;
            return RedirectToAction("Tags");
        }

        public ActionResult Comments()
        {
            return View(this.commentRepository.GetAll().OrderBy(c => c.CreatedDate));
        }

        public ActionResult CreateComment()
        {
            var viewModel = this.commentTasks.CreateEditViewModel();

            return this.View("EditComment", viewModel);
        }

        public ActionResult EditComment(int id)
        {
            return View(this.commentTasks.CreateEditViewModel(id));
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        public ActionResult EditComment(Comment comment)
        {
            if (ModelState.IsValid)
            {
                var confirmation = this.commentTasks.SaveOrUpdate(comment);

                if (confirmation.WasSuccessful)
                {
                    TempData["message"] = confirmation.Message;
                    return RedirectToAction("Comments");
                }

                ViewData["message"] = confirmation.Message;
            }

            return View(this.commentTasks.CreateEditViewModel(comment));
        }

        [HttpPost]
        [ValidateAntiForgeryToken]
        public ActionResult DeleteComment(int id)
        {
            var confirmation = this.commentTasks.Delete(id);
            TempData["message"] = confirmation.Message;
            return RedirectToAction("Comments");
        }
    }
}
